package com.ryskoo.permission.menu.repository;

import com.ryskoo.common.constant.CacheConstant;
import com.ryskoo.framework.core.repository.BasicRedisImpl;
import com.ryskoo.framework.core.utils.RedisUtil;
import com.ryskoo.permission.managerrolerel.repository.IManagerRoleRelRepository;
import com.ryskoo.permission.menu.domain.MenuPO;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Primary;
import org.springframework.stereotype.Repository;
import org.springframework.util.StringUtils;

import javax.annotation.PostConstruct;
import java.util.ArrayList;
import java.util.List;

@Primary
@Repository
public class MenuRedisImpl extends BasicRedisImpl<MenuPO> implements IMenuRepository {
	@Autowired
	private RedisUtil redisClient;

	@Autowired
	private IMenuRepository menuRepository;
	
	//注入管理员和角色关联service
	@Autowired
	private IManagerRoleRelRepository managerRoleRelRepository;

	@PostConstruct
	public void init() {
		this.setRedisClient(redisClient);
		this.setDao(menuRepository);
	}

	public MenuRedisImpl() {
		super(CacheConstant.PERMISSION_MENU_KEY);
	}

	/**
	 * 重写create方法，刷新缓存
	 * 
	 * 如果编辑的是一级菜单，则删除一级菜单的缓存，如果是其他菜单，则删除上级菜单的缓存
	 * 
	 */
	@Override
	public void create(MenuPO m) {
		if (StringUtils.isEmpty(m.getParentId())) {
			if (0 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU");
			} else if (1 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU");
			} 
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU");
		} else {
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + m.getParentId());
		}
		super.create(m);
	}
	
	
	/**
	 * 重写update方法，刷新缓存
	 * 
	 * 如果编辑的是一级菜单，则删除一级菜单的缓存，如果是其他菜单，则删除上级菜单的缓存
	 * 
	 * 删除编辑之前的父菜单
	 */
	@Override
	public void update(MenuPO m) {
		if (StringUtils.isEmpty(m.getParentId())) {
			if (0 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU");
			} else if (1 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU");
			} 
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU");
		} else {
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + m.getParentId());
		}
		
		//删除编辑之前的父菜单缓存
		MenuPO oldMenu = super.getByUuid(m.getUuid());
		if (StringUtils.isEmpty(oldMenu.getParentId())) {
			if (0 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU");
			} else if (1 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU");
			} 
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU");
		} else {
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + oldMenu.getParentId());
		}
		
        super.merge(m);
	}
	
	
	/**
	 * 重写delete方法，刷新缓存
	 * 删除子菜单集合缓存
	 */
	@Override
	public void delete(MenuPO m) {
		if (StringUtils.isEmpty(m.getParentId())) {
			if (0 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU");
			} else if (1 == m.getType()) {
				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU");
			} 
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU");
		} else {
			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + m.getParentId());
		}
        super.delete(m);
	}

	
	/**
	 * 重写delete方法，刷新缓存
	 * 删除子菜单集合缓存
	 */
	@Override
	public void deletes(List<String> needDeleteUuids) {
        for (String deleteUuid : needDeleteUuids) {
        	MenuPO m = super.getByUuid(deleteUuid);
        	if (StringUtils.isEmpty(m.getParentId())) {
    			if (0 == m.getType()) {
    				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU");
    			} else if (1 == m.getType()) {
    				redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU");
    			} 
    			    redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU");
    		} else {
    			redisClient.remove(CacheConstant.PERMISSION_MENU_LIST_KEY + m.getParentId());
    		}
        }
        super.deletes(needDeleteUuids);
	}
	
	
	
	/**
	 * 根据菜单类型和父菜单ID查询菜单（包括子菜单集合）
	 * 如果父菜单为空，则查询一级菜单
	 * 先根据父菜单的ID从缓存获取子菜单集合，如果缓存为空，则从数据库查询
	 * @param menuType
	 * @param parentId
	 * @return
	 */
	@Override
	public List<MenuPO> getMenus(String menuType, String parentId) {
		String cacheKey = "";
		//如果parentId为空，查询一级菜单
		if (StringUtils.isEmpty(parentId)) {
			//根据菜单类型查询菜单
			if ("0".equals(menuType)) {
				cacheKey = CacheConstant.PERMISSION_MENU_LIST_KEY + "PLAT_TOPMENU";
			} else if ("1".equals(menuType)) {
				cacheKey = CacheConstant.PERMISSION_MENU_LIST_KEY + "STORE_TOPMENU";
			} else {
				cacheKey = CacheConstant.PERMISSION_MENU_LIST_KEY + "ALL_TOPMENU";
			}
		} else {
			cacheKey =  CacheConstant.PERMISSION_MENU_LIST_KEY + "" + parentId;
		}
		
		//根据父菜单ID缓存获取菜单集合
		Object object = redisClient.getSession(cacheKey);
		
		if (object != null) {
			List<MenuPO> cacheList = (List<MenuPO>)object;
			return cacheList;
		}
		
		//获取菜单的uuid，再根据uuid从缓存获取对象
		List<String> uuids = menuRepository.getMenuUuids(menuType, parentId);
		List<MenuPO> list = new ArrayList<MenuPO>();

		if (uuids != null && uuids.size() > 0) {
			for (String uuid : uuids) {
				MenuPO po = menuRepository.getByUuid(uuid);
				if (po != null) {
					list.add(po);
				}
			}
		}
		
		//将结果放入缓存
		redisClient.setExpireSession(cacheKey, list, null);
		
		return list;
	}

	/**
	 * 根据菜单类型和父菜单查询菜单的uuid
	 * 
	 * @param menuType
	 * @return
	 */
	@Override
	public List<String> getMenuUuids(String menuType, String parentId) {
		return menuRepository.getMenuUuids(menuType, parentId);
	}

	/**
	 * 根据管理员id获取此管理员可见的菜单列表
	 *
	 * @param managerId 管理员id
	 * @param menuType 菜单类型  0：平台菜单  1：商户菜单
	 * @return 菜单列表 {@link List}&lt;{@link MenuPO}&gt;
	 */
	@SuppressWarnings("unchecked")
	@Override
	public List<MenuPO> getMenuByManagerId(String managerId, int menuType) {
		List<MenuPO> returnList = new ArrayList<>();
		//获取管理员的角色
		List<String> roleIds = managerRoleRelRepository.getRoleUuidsByManagerId(managerId);
		if (roleIds != null && roleIds.size() > 0) {
			for (String roleId : roleIds) {
				//通过角色id缓存获取菜单
				List<MenuPO> menuList = (List<MenuPO> )redisClient.getSession(CacheConstant.PMS_ROLE_MENU_KEY + roleId);
				if (null != menuList && menuList.size() > 0) {
					returnList.addAll(menuList);
				}
			}
		}
		return returnList;
	}

	/**
	 * 根据角色id获取此管理员可见的菜单列表
	 *
	 * @param roleId   角色id
	 * @param menuType 菜单类型  0：平台菜单  1：商户菜单
	 * @return 菜单列表 {@link List}&lt;{@link MenuPO}&gt;
	 */
	@Override
	public List<MenuPO> getMenuByRoleId(String roleId, int menuType) {
		return menuRepository.getMenuByRoleId(roleId, menuType);
	}
}
